﻿using Microsoft.Extensions.Hosting;
using Serilog;
using Serilog.Events;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Mrhd.Core.Extensions
{
    /// <summary>
    /// 系统层面扩展
    /// </summary>
    public static class SystemExtensions
    {
        /// <summary>
        /// 使用Serilog记录日志
        /// </summary>
        /// <param name="host"></param>
        /// <param name="action"></param>
        /// <returns></returns>
        public static IHostBuilder UseSerilog(this IHostBuilder host, Action<LoggerConfiguration> action = null)
        {
            if (action == null)
            {
                action = config =>
                {
                    // 按时间创建文件夹
                    var date = DateTime.Now.ToString("yyyy-MM-dd");
                    // 输出模板
                    var outputTemplate = "{NewLine}【{Level:u3}】 {Timestamp:yyyy-MM-dd HH:mm:ss.fff}" +
                     "{NewLine}#Msg# {Message:lj}" +
                     "{NewLine}#Pro# {Properties:j}" +
                     "{NewLine}#Exc# {Exception}" +
                    new string('-', 50);

                    // 1.输出所有restrictedToMinimumLevel：LogEventLevel类型
                    config
                        //.MinimumLevel.Debug() // 所有Sink的最小记录级别
                        //.MinimumLevel.Override("Microsoft", LogEventLevel.Fatal)
                        //.Enrich.FromLogContext()
                        // 将控制台接收器添加到管道
                        .WriteTo.Console()
                        // 将日志文件添加到管道
                        .WriteTo.File($"log/{date}/application.log",
                                outputTemplate: outputTemplate,
                                // 最小日志记录级别
                                restrictedToMinimumLevel: LogEventLevel.Information,
                                // 文件字符编码
                                encoding: Encoding.UTF8,
                                // 日志按日保存，这样会在文件名称后自动加上日期后缀
                                rollingInterval: RollingInterval.Day
                                //rollOnFileSizeLimit: true,          // 限制单个文件的最大长度
                                //retainedFileCountLimit: 10,         // 最大保存文件数,等于null时永远保留文件。
                                //fileSizeLimitBytes: 10 * 1024,      // 最大单个文件大小
                            );


                    // 2. 定义一个子记录器，仅输出 LogEventLevel.Debug 类型（因为默认级别是information，此处不会有日志记录）
                    config.WriteTo.Logger(lg => lg.Filter.ByIncludingOnly(evt => evt.Level == LogEventLevel.Debug)//筛选过滤
                        .WriteTo.File($"log/{date}/{LogEventLevel.Debug}.log",
                            outputTemplate: outputTemplate,
                            // 日志按日保存，这样会在文件名称后自动加上日期后缀
                            rollingInterval: RollingInterval.Day,
                            // 文件字符编码
                            encoding: Encoding.UTF8
                         )
                     );

                    // 3. 定义一个子记录器，仅输出 LogEventLevel.Error 类型
                    config.WriteTo.Logger(lg => lg.Filter.ByIncludingOnly(evt => evt.Level == LogEventLevel.Error)
                        .WriteTo.File($"log/{date}/{LogEventLevel.Error}.log",
                            outputTemplate: outputTemplate,
                            rollingInterval: RollingInterval.Day,
                            encoding: Encoding.UTF8
                         )
                     );
                };
            }
            host.UseSerilogDefault(action);
            return host;
        }

    }
}
